package com.mingtu.dzpatrol.activity;

import android.app.ActionBar;
import android.content.res.Configuration;
import android.graphics.Rect;
import android.graphics.SurfaceTexture;
import android.os.Build;
import android.view.TextureView;
import android.view.View;
import android.view.WindowManager;
import android.widget.ProgressBar;
import android.widget.TextView;

import androidx.annotation.NonNull;

import com.blankj.utilcode.util.ToastUtils;
import com.gyf.immersionbar.ImmersionBar;
import com.hikvision.hatomplayer.DefaultHatomPlayer;
import com.hikvision.hatomplayer.HatomPlayer;
import com.hikvision.hatomplayer.PlayCallback;
import com.hikvision.hatomplayer.PlayConfig;
import com.hikvision.hatomplayer.core.HeaderParams;


import com.mingtu.dzpatrol.R;
import com.mingtu.dzpatrol.base.BaseActivity;
import com.mingtu.dzpatrol.utils.MyLogUtil;

import com.mingtu.hikvideo2.bean.PlaybackBean;
import com.mingtu.hikvideo2.model.RecordSegment;
import com.mingtu.hikvideo2.utils.CalendarUtil;
import com.mingtu.hikvideo2.utils.PlayerStatus;
import com.mingtu.hikvideo2.widget.TimeBarView;
import com.mingtu.hikvideo2.widget.window.PlayTextureView;

import java.text.DecimalFormat;
import java.text.MessageFormat;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.HashMap;
import java.util.List;

public class NewPlaybackActivity extends BaseActivity implements TextureView.SurfaceTextureListener {

    private TimeBarView timeBar;
    private PlayerStatus mPlayerStatus = PlayerStatus.IDLE;//默认闲置
    /**
     * 电子放大倍数格式化,显示小数点后一位
     */
    private DecimalFormat decimalFormat;
    private String TAG = "VideoPlay";
    private String url;
    private PlayTextureView playTextureView;
    private ProgressBar progressBar;
    private Calendar mSeekCalendar = Calendar.getInstance();
    private String startTime = "";
    private String stopTime = "";

    /**
     * 每隔400ms获取一次当前回放的系统时间
     * 更新时间条上的OSD时间
     */
    private final Runnable mGetOSDTimeTask = new Runnable() {
        @Override
        public void run() {
            long osdTime = hatomPlayer.getOSDTime();
            if (osdTime > -1) {
                timeBar.setCurrentTime(osdTime);
            }

            startUpdateTime();
        }
    };
    private List<PlaybackBean.DataBean.ListBean> listBeans;
    private HatomPlayer hatomPlayer;
    private TextView zoomText;
    private TextView errorText;

    @Override
    protected int getLayoutId() {
        return R.layout.activity_new_play_back;
    }

    @Override
    protected void initView() {
//        initPlayWindowContainer(); //横竖屏切换的时候有bug,暂时隐藏
        playTextureView = findViewById(R.id.textureView);
        timeBar = findViewById(R.id.time_bar);
        playTextureView.setSurfaceTextureListener(this);
        zoomText = (TextView) findViewById(R.id.zoomText);
        progressBar = findViewById(R.id.loadingView);
        errorText = (TextView) findViewById(R.id.errorText);
        getTopLeftButton().setImageResource(R.mipmap.icon_back_white);
        setModuleTitleColor(R.color.white);
        setTitleBarBackground(getResources().getColor(R.color.black));
    }

    @Override
    protected void initData() {

        url = getIntent().getStringExtra("videoUrl");
        String title = getIntent().getStringExtra("title");
        setModuleTitle(title);

        try {
            ArrayList<Object> list = (ArrayList<Object>) getIntent().getSerializableExtra("object"); //存放视频片段对象
            listBeans = (List<PlaybackBean.DataBean.ListBean>) list.get(0);
            initTimeBarView();
        } catch (Exception e) {
            ToastUtils.showLong("暂无回放视频哦~");
            e.printStackTrace();
        }

    }


    @Override
    protected void getData() {
        //沉侵式状态栏
        ImmersionBar immersionBar = ImmersionBar.with(this);
//        immersionBar.statusBarDarkFont(true);
        immersionBar.autoStatusBarDarkModeEnable(true);
        immersionBar.barColor(R.color.black);
        immersionBar.init();

    }

    @Override
    public void onConfigurationChanged(Configuration newConfig) {
        super.onConfigurationChanged(newConfig);
//        layoutViews();
    }

    @Override
    protected void onResume() {
        super.onResume();
        //TODO 注意:APP前后台切换时 SurfaceTextureListener可能在有某些 华为手机 上不会回调，例如：华为P20，所以我们在这里手动调用
        MyLogUtil.e("textureView", playTextureView.isAvailable() + "");
        if (playTextureView.isAvailable()) {
            onSurfaceTextureAvailable(playTextureView.getSurfaceTexture(), playTextureView.getWidth(), playTextureView.getHeight());
        }
    }

    @Override
    protected void onPause() {
        super.onPause();
        //TODO 注意:APP前后台切换时 SurfaceTextureListener可能在有某些 华为手机 上不会回调，例如：华为P20，所以我们在这里手动调用
        if (playTextureView.isAvailable()) {
            onSurfaceTextureDestroyed(playTextureView.getSurfaceTexture());
        }
    }

    @Override
    protected void onDestroy() {
        super.onDestroy();

        if (hatomPlayer != null) {
            hatomPlayer.stop();
        }
        if (playTextureView.isAvailable()) {
            onSurfaceTextureDestroyed(playTextureView.getSurfaceTexture());
        }

        cancelUpdateTime();
    }

    /*************************TextureView.SurfaceTextureListener 接口的回调方法********************/
    //TODO 注意:APP前后台切换时 SurfaceTextureListener可能在有某些华为手机上不会回调，例如：华为P20，因此我们需要在Activity生命周期中手动调用回调方法
    @Override
    public void onSurfaceTextureAvailable(SurfaceTexture surface, int width, int height) {
        if (mPlayerStatus == PlayerStatus.STOPPING) {
            //恢复处于暂停播放状态的窗口
            startPreview();
            MyLogUtil.e(TAG, "onSurfaceTextureAvailable: startRealPlay");
        } else if (mPlayerStatus == PlayerStatus.IDLE) {
            startPreview();
        }
    }

    @Override
    public void onSurfaceTextureSizeChanged(SurfaceTexture surface, int width, int height) {

    }

    @Override
    public boolean onSurfaceTextureDestroyed(SurfaceTexture surface) {
        if (mPlayerStatus == PlayerStatus.SUCCESS) {
            mPlayerStatus = PlayerStatus.STOPPING;//暂停播放，再次进入时恢复播放
            stopPlay();
            cancelUpdateTime();
            MyLogUtil.e(TAG, "onSurfaceTextureDestroyed: stopPlay");
        }
        return false;
    }

    @Override
    public void onSurfaceTextureUpdated(SurfaceTexture surface) {

    }


    /**
     * 屏幕方向变化后重新布局View
     */
//    private void layoutViews() {
//        ViewGroup.LayoutParams layoutParams = frameLayout.getLayoutParams();
//        if (ScreenUtils.isPortrait()) {
//            //先显示系统状态栏
//            showSystemUI();
//            //再显示控制按钮区域
//            layoutParams.height = SizeUtils.dp2px(250f);
//
//        } else if (ScreenUtils.isLandscape()) {
//            //隐藏系统UI
//            hideSystemUI();
//            layoutParams.height = ScreenUtils.getScreenHeight();
//        }
//    }

    /**
     * 隐藏系统ui
     */
    private void hideSystemUI() {
        //隐藏ActionBar 如果使用了NoActionBar的Theme则不需要隐藏actionBar
//        android.app.ActionBar actionBar = getSupportActionBar();
//        if (actionBar != null) {
//            actionBar.hide();
//        }

        //TODO：View.setSystemUiVisibility(int visibility)中，visibility是Mode与Layout任意取值的组合，可传入的实参为：

        // Mode属性
        //View.SYSTEM_UI_FLAG_LOW_PROFILE：状态栏显示处于低能显示状态(low profile模式)，状态栏上一些图标显示会被隐藏。
        //View.SYSTEM_UI_FLAG_FULLSCREEN：Activity全屏显示，且状态栏被隐藏覆盖掉。等同于（WindowManager.LayoutParams.FLAG_FULLSCREEN）
        //View.SYSTEM_UI_FLAG_HIDE_NAVIGATION：隐藏虚拟按键(导航栏)。有些手机会用虚拟按键来代替物理按键。
        //View.SYSTEM_UI_FLAG_IMMERSIVE：这个flag只有当设置了SYSTEM_UI_FLAG_HIDE_NAVIGATION才起作用。
        // 如果没有设置这个flag，任意的View相互动作都退出SYSTEM_UI_FLAG_HIDE_NAVIGATION模式。如果设置就不会退出。
        //View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY：这个flag只有当设置了SYSTEM_UI_FLAG_FULLSCREEN | SYSTEM_UI_FLAG_HIDE_NAVIGATION 时才起作用。
        // 如果没有设置这个flag，任意的View相互动作都坏退出SYSTEM_UI_FLAG_FULLSCREEN | SYSTEM_UI_FLAG_HIDE_NAVIGATION模式。如果设置就不受影响。

        // Layout属性
        //View.SYSTEM_UI_FLAG_LAYOUT_STABLE： 保持View Layout不变，隐藏状态栏或者导航栏后，View不会拉伸。
        //View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN：让View全屏显示，Layout会被拉伸到StatusBar下面，不包含NavigationBar。
        //View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION：让View全屏显示，Layout会被拉伸到StatusBar和NavigationBar下面。
        View decorView = getWindow().getDecorView();
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
            decorView.setSystemUiVisibility(
                    View.SYSTEM_UI_FLAG_LOW_PROFILE
                            | View.SYSTEM_UI_FLAG_HIDE_NAVIGATION // hide nav bar
                            | View.SYSTEM_UI_FLAG_FULLSCREEN // hide status bar
                            | View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY
            );
        }
        //解决在华为手机上横屏时，状态栏不消失的问题
        getWindow().addFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN); //隐藏状态栏

    }

    /**
     * 显示系统UI
     */
    private void showSystemUI() {
        //显示ActionBar 如果使用了NoActionBar的Theme则不需要显示actionBar
//        ActionBar actionBar = getSupportActionBar();
//        if (actionBar != null) {
//            actionBar.show();
//        }
        View decorView = getWindow().getDecorView();
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
            // This snippet shows the system bars. It does this by removing all the flags
            // except for the ones that make the content appear under the system bars.
            decorView.setSystemUiVisibility(View.SYSTEM_UI_FLAG_VISIBLE);
        }
        //解决在华为手机上横屏时，状态栏不消失的问题
        getWindow().clearFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN); //显示状态栏
    }

    /**
     * 开始预览
     */
    private void startPreview() {
        //创建HatomPlayer实例
        hatomPlayer = new DefaultHatomPlayer();
        playTextureView.setOnZoomListener(new PlayTextureView.OnZoomListener() {
            @Override
            public void onZoomChange(Rect oRect, Rect curRect) {
                hatomPlayer.openDigitalZoom(oRect, curRect);
            }
        });

        final DecimalFormat decimalFormat = new DecimalFormat("0.0");
        //设置电子放大倍率监听
        playTextureView.setOnZoomScaleListener(new PlayTextureView.OnZoomScaleListener() {
            @Override
            public void onZoomScale(float scale) {
                if (scale < 1.0f) {
                    //如果已经开启了电子放大且倍率小于1就关闭电子放大
                    hatomPlayer.closeDigitalZoom();
                }
                if (scale >= 1.0f) {
                    String text = MessageFormat.format("{0}X", decimalFormat.format(Double.valueOf(scale + "")));
                    zoomText.setText(text);
                }

            }
        });

        if (listBeans != null) {
            int liseSize = listBeans.size();
            if (liseSize > 0) {
                if (liseSize == 1) {
                    startTime = listBeans.get(0).getBeginTime();
                    stopTime = listBeans.get(0).getEndTime();
                }
                if (liseSize > 1) {
                    startTime = listBeans.get(0).getBeginTime();
                    stopTime = listBeans.get(liseSize - 1).getEndTime();
                }
            }
        }

        HashMap<String, String> header = new HashMap<String, String>();
        header.put(HeaderParams.START_TIME, startTime);
        header.put(HeaderParams.END_TIME, stopTime);


        SurfaceTexture surfaceTexture = playTextureView.getSurfaceTexture();
        hatomPlayer.setSurfaceTexture(surfaceTexture);

        //播放前设置播放配置(可选)
        PlayConfig playConfig = new PlayConfig();
        playConfig.hardDecode = true;//使用硬解码
        playConfig.privateData = false;//关闭智能信息
        hatomPlayer.setPlayConfig(playConfig);
        hatomPlayer.setDataSource(url, header);
        hatomPlayer.setPlayStatusCallback(new PlayCallback.PlayStatusCallback() {
            @Override
            public void onPlayerStatus(@NonNull PlayCallback.Status status, final String error) {

                runOnUiThread(new Runnable() {
                    @Override
                    public void run() {
                        progressBar.setVisibility(View.GONE);
                    }
                });

                if (status == PlayCallback.Status.SUCCESS) {//播放成功
                    mPlayerStatus = PlayerStatus.SUCCESS;
                    runOnUiThread(new Runnable() {
                        @Override
                        public void run() {
                            errorText.setVisibility(View.GONE);
                            playTextureView.setKeepScreenOn(true);//保持亮屏
                        }
                    });

                    timeBar.setCurrentTime(hatomPlayer.getOSDTime());
                    startUpdateTime();//开始刷新回放时间
                } else if (status == PlayCallback.Status.FAILED) {//播放失败
                    cancelUpdateTime();
                    mPlayerStatus = PlayerStatus.FAILED;

                    runOnUiThread(new Runnable() {
                        @Override
                        public void run() {
                            errorText.setVisibility(View.VISIBLE);
                            errorText.setText("回放失败，" + error);
                        }
                    });

                } else if (status == PlayCallback.Status.EXCEPTION) {//取流异常
                    if (mGetOSDTimeTask != null) {
                        cancelUpdateTime();
                    }
                    mPlayerStatus = PlayerStatus.EXCEPTION;
                    stopPlay();//TODO 注意:异常时关闭取流
                    runOnUiThread(new Runnable() {
                        @Override
                        public void run() {
                            errorText.setVisibility(View.VISIBLE);
                            errorText.setText("回放失败，" + error);
                        }
                    });
                } else if (status == PlayCallback.Status.FINISH) {//录像回放结束
                    mPlayerStatus = PlayerStatus.FINISH;
                    ToastUtils.showShort("没有录像片段了");
                }

            }
        });

        new Thread(new Runnable() {
            @Override
            public void run() {
                //开启预览
                //此方法需要在子线程中执行
                hatomPlayer.start();
            }
        }).start();
    }

    /**
     * 开始刷新回放时间
     */
    private void startUpdateTime() {
        try {
            errorText.getHandler().postDelayed(mGetOSDTimeTask, 400);
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    /**
     * 停止刷新回放时间
     */
    private void cancelUpdateTime() {
        try {
            errorText.getHandler().removeCallbacks(mGetOSDTimeTask);
        } catch (Exception e) {
            e.printStackTrace();
        }
    }


    /**
     * 停止播放
     */
    private void stopPlay() {
        new Thread(new Runnable() {
            @Override
            public void run() {
                //开启预览
                //此方法需要在子线程中执行
                if (hatomPlayer != null) {
                    hatomPlayer.stop();
                }
            }
        }).start();

    }

    private void initTimeBarView() {
        List<RecordSegment> recordSegmentList = new ArrayList<>();
        if (listBeans != null) {
            if (listBeans.size() > 0) {

                for (int i = 0; i < listBeans.size(); i++) {
                    String beginTim = listBeans.get(i).getBeginTime();
                    String endTim = listBeans.get(i).getEndTime();

                    RecordSegment recordSegment = new RecordSegment();
                    recordSegment.setBeginTime(beginTim);
                    recordSegment.setEndTime(endTim);

                    recordSegmentList.add(recordSegment);
                }

                //TODO 注意:TimeBarView中数据为你从服务器端获取到的录像片段列表
                timeBar.addFileInfoList(recordSegmentList);
                timeBar.setTimeBarCallback(new TimeBarView.TimePickedCallBack() {
                    @Override
                    public void onMoveTimeCallback(long currentTime) {
                        Calendar calendar = Calendar.getInstance();
                        calendar.setTimeInMillis(currentTime);
                        MyLogUtil.e("timeBar", "onMoveTimeCallback==" + CalendarUtil.calendarToyyyy_MM_dd_T_HH_mm_SSSZ(calendar));
                    }

                    @Override
                    public void onBarMoving(long currentTime) {
                        Calendar calendar = Calendar.getInstance();
                        calendar.setTimeInMillis(currentTime);
                    }

                    @Override
                    public void onTimePickedCallback(long currentTime) {
                        Calendar calendar = Calendar.getInstance();
                        calendar.setTimeInMillis(currentTime);
                        MyLogUtil.e("timeBar", "onTimePickedCallback==" + CalendarUtil.calendarToyyyy_MM_dd_T_HH_mm_SSSZ(calendar));

                        long beginTimeMillis = CalendarUtil.yyyy_MM_dd_T_HH_mm_SSSZToLong(startTime);
                        long endTimeMillis = CalendarUtil.yyyy_MM_dd_T_HH_mm_SSSZToLong(stopTime);

                        if (currentTime > endTimeMillis || currentTime < beginTimeMillis) {
//                            cancelUpdateTime();
                            ToastUtils.showLong("抱歉，回放时间点不在回放范围哦~");
                            return;
                        }
                        //TODO 注意: 定位操作的时间要在录像片段开始时间和结束时间之内，不再范围内不要执行以下操作
                        mSeekCalendar.setTimeInMillis(currentTime);
                        final String start = CalendarUtil.calendarToyyyy_MM_dd_T_HH_mm_SSSZ(mSeekCalendar);
                        MyLogUtil.e(TAG, "onTimePickedCallback: currentTime = " + start);

                        progressBar.setVisibility(View.VISIBLE);
                        new Thread(new Runnable() {
                            @Override
                            public void run() {
                                cancelUpdateTime();//seek时停止刷新时间
                                //TODO:iSC V1.2.0平台开始推荐使用 yyyy_MM_dd_T_HH_mm_SSSZ的起止时间格式
                                if (mPlayerStatus == PlayerStatus.EXCEPTION || mPlayerStatus == PlayerStatus.FAILED || mPlayerStatus == PlayerStatus.IDLE) {
                                    progressBar.setVisibility(View.GONE);
                                    ToastUtils.showLong("播放状态异常，不能拖动回放哦~");
                                    return;
                                }
                                hatomPlayer.seekPlayback(start);
                            }
                        }).start();
                    }

                    @Override
                    public void onMaxScale() {

                    }

                    @Override
                    public void onMinScale() {

                    }
                });
            }
        }


    }
}